package network;

import com.cedarsoftware.util.io.JsonReader;
import server.Server;
import java.io.*;
import java.util.concurrent.PriorityBlockingQueue;
import java.util.logging.Level;
import java.util.logging.Logger;
import packet.CommandRequest;

/**
 * Listens on network and drops packets to queue for processing
 * @author Joel Garboden
 */
public class Net2QRunnable implements Runnable
{
  Server loggingServer;

  private String identifier;
  private boolean active = true;

  private JsonReader netIn;

  private PriorityBlockingQueue<CommandRequest> srvQ;

  /**
   * Constructor for lobby mode
   * @param netIn incoming network stream
   * @param srvQ queue to drop packets to for processing
   */
  public Net2QRunnable(int ID, JsonReader netIn, PriorityBlockingQueue<CommandRequest> srvQ)
  {
    if (ID < 0)
    {
      identifier = "a lobby client";
    }
    else
    {
      identifier = "client " + ID;
    }
    this.netIn = netIn;
    this.srvQ = srvQ;
  }

  /**
   * Constructor for game mode
   * @param ID client ID
   * @param netIn incoming network stream
   * @param srvQ queue to drop packets to for processing
   */
  public Net2QRunnable(String identifier, JsonReader netIn, PriorityBlockingQueue<CommandRequest> srvQ)
  {
    this.identifier = identifier;
    this.netIn = netIn;
    this.srvQ = srvQ;
  }

  /**
   * Enables logging to current server
   * @param server server to dump logs to
   */
  public void setLoggingServer(Server server)
  {
    loggingServer = server;
  }

  /**
   * Mutator
   * @param active activity state
   */
  public void setActive(boolean active)
  {
    this.active = active;
  }

  /**
   * Accessor
   * @return activity state
   */
  public boolean isActive()
  {
    return active;
  }

  /**
   * Continuously listens on incoming network stream for packets, <br/>
   * and drops them to the server queue
   */
  @Override
  public void run()
  {
    CommandRequest cmdreq;
    try
    {
      try
      {
        while(active)
        {
          cmdreq = (CommandRequest)netIn.readObject();
          srvQ.add(cmdreq);
          if(loggingServer != null)
            loggingServer.postLogMsg("Recieving from " + identifier + " " + cmdreq.toString());
          else
            System.out.println("Recieving from " + identifier + " " + cmdreq.toString());
        }

      }
      catch (EOFException e)
      {
        //srvQ.add(new PlayerQuitReq(identifier));
        System.out.println("Net2QRunnable inner: " + e);
        return;
      }

    }
    catch (IOException e)
    {
      System.out.println("Net2QRunnable outer: " + e);
    }
    catch (Throwable ex)
    {
      Logger.getLogger(Net2QRunnable.class.getName()).log(Level.SEVERE, "Net2QRunnable throwable", ex);
    }
    //srvQ.add(new PlayerQuitReq(identifier));
  }
}
